Code Coverage |
||||||||||
Classes and Traits |
Functions and Methods |
Lines |
||||||||
| Total | |
100.00% |
1 / 1 |
|
100.00% |
36 / 36 |
CRAP | |
100.00% |
178 / 178 |
| AbstractPath | |
100.00% |
1 / 1 |
|
100.00% |
36 / 36 |
70 | |
100.00% |
178 / 178 |
| __construct($atoms, $hasTrailingSeparator = null) | |
100.00% |
1 / 1 |
2 | |
100.00% |
6 / 6 |
|||
| atoms() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| sliceAtoms($index, $length = null) | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| hasAtoms() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| hasTrailingSeparator() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| string() | |
100.00% |
1 / 1 |
2 | |
100.00% |
3 / 3 |
|||
| __toString() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| name() | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| nameAtoms() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| sliceNameAtoms($index, $length = null) | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| nameWithoutExtension() | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| namePrefix() | |
100.00% |
1 / 1 |
1 | |
100.00% |
2 / 2 |
|||
| nameSuffix() | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| extension() | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| hasExtension() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| parent() | |
100.00% |
1 / 1 |
1 | |
100.00% |
5 / 5 |
|||
| stripTrailingSlash() | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| stripExtension() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| stripNameSuffix() | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| joinAtoms($atom) | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| joinAtomSequence($atoms) | |
100.00% |
1 / 1 |
2 | |
100.00% |
6 / 6 |
|||
| join(RelativePathInterface $path) | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| joinExtensions($extension) | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| joinExtensionSequence($extensions) | |
100.00% |
1 / 1 |
3 | |
100.00% |
13 / 13 |
|||
| replace($index, $replacement, $length = null) | |
100.00% |
1 / 1 |
3 | |
100.00% |
11 / 11 |
|||
| suffixName($suffix) | |
100.00% |
1 / 1 |
2 | |
100.00% |
4 / 4 |
|||
| prefixName($prefix) | |
100.00% |
1 / 1 |
2 | |
100.00% |
4 / 4 |
|||
| replaceName($name) | |
100.00% |
1 / 1 |
4 | |
100.00% |
13 / 13 |
|||
| replaceNameWithoutExtension($nameWithoutExtension) | |
100.00% |
1 / 1 |
2 | |
100.00% |
5 / 5 |
|||
| replaceNamePrefix($namePrefix) | |
100.00% |
1 / 1 |
1 | |
100.00% |
1 / 1 |
|||
| replaceNameSuffix($nameSuffix) | |
100.00% |
1 / 1 |
4 | |
100.00% |
14 / 14 |
|||
| replaceExtension($extension) | |
100.00% |
1 / 1 |
6 | |
100.00% |
18 / 18 |
|||
| replaceNameAtoms($index, $replacement, $length = null) | |
100.00% |
1 / 1 |
3 | |
100.00% |
9 / 9 |
|||
| normalizeAtoms($atoms) | |
100.00% |
1 / 1 |
2 | |
100.00% |
6 / 6 |
|||
| validateAtom($atom) | |
100.00% |
1 / 1 |
3 | |
100.00% |
5 / 5 |
|||
| createPath( $atoms, $isAbsolute, $hasTrailingSeparator = null ) | |
100.00% |
1 / 1 |
2 | |
100.00% |
7 / 7 |
|||
| <?php | |
| /* | |
| * This file is part of the Pathogen package. | |
| * | |
| * Copyright © 2013 Erin Millard | |
| * | |
| * For the full copyright and license information, please view the LICENSE | |
| * file that was distributed with this source code. | |
| */ | |
| namespace Eloquent\Pathogen; | |
| abstract class AbstractPath implements PathInterface | |
| { | |
| /** | |
| * @param mixed<string> $atoms | |
| * @param boolean|null $hasTrailingSeparator | |
| * | |
| * @throws Exception\InvalidPathAtomExceptionInterface | |
| */ | |
| public function __construct($atoms, $hasTrailingSeparator = null) | |
| { | |
| if (null === $hasTrailingSeparator) { | |
| $hasTrailingSeparator = false; | |
| } | |
| $this->atoms = $this->normalizeAtoms($atoms); | |
| $this->hasTrailingSeparator = $hasTrailingSeparator === true; | |
| } | |
| // Implementation of PathInterface ========================================= | |
| /** | |
| * Returns the atoms of this path as an array of strings. | |
| * | |
| * For example, the path '/foo/bar' has the atoms 'foo' and 'bar'. | |
| * | |
| * @return array<integer,string> | |
| */ | |
| public function atoms() | |
| { | |
| return $this->atoms; | |
| } | |
| /** | |
| * Returns a subsequence of the atoms of this path as an array of strings. | |
| * | |
| * @param integer $index | |
| * @param integer|null $length | |
| * | |
| * @return array<integer,string> | |
| */ | |
| public function sliceAtoms($index, $length = null) | |
| { | |
| $atoms = $this->atoms(); | |
| if (null === $length) { | |
| $length = count($atoms); | |
| } | |
| return array_slice($atoms, $index, $length); | |
| } | |
| /** | |
| * Returns true is at least one atom is present. | |
| * | |
| * @return boolean | |
| */ | |
| public function hasAtoms() | |
| { | |
| return count($this->atoms()) > 0; | |
| } | |
| /** | |
| * Returns true if this path ends with a path separator. | |
| * | |
| * @return boolean | |
| */ | |
| public function hasTrailingSeparator() | |
| { | |
| return $this->hasTrailingSeparator; | |
| } | |
| /** | |
| * Returns a string representation of this path. | |
| * | |
| * @return string | |
| */ | |
| public function string() | |
| { | |
| return | |
| implode(static::ATOM_SEPARATOR, $this->atoms()) . | |
| ($this->hasTrailingSeparator() ? static::ATOM_SEPARATOR : '') | |
| ; | |
| } | |
| /** | |
| * Returns a string representation of this path. | |
| * | |
| * @return string | |
| */ | |
| public function __toString() | |
| { | |
| return $this->string(); | |
| } | |
| /** | |
| * Returns the last atom of this path. | |
| * | |
| * If this path has no atoms, an empty string is returned. | |
| * | |
| * @return string | |
| */ | |
| public function name() | |
| { | |
| $atoms = $this->atoms(); | |
| $numAtoms = count($atoms); | |
| if ($numAtoms > 0) { | |
| return $atoms[$numAtoms - 1]; | |
| } | |
| return ''; | |
| } | |
| /** | |
| * Returns the atoms of this path's name as an array of strings. | |
| * | |
| * For example, the path name 'foo.bar' has the atoms 'foo' and 'bar'. | |
| * | |
| * @return array<integer,string> | |
| */ | |
| public function nameAtoms() | |
| { | |
| return explode(static::EXTENSION_SEPARATOR, $this->name()); | |
| } | |
| /** | |
| * Returns a subsequence of the atoms of this path's name as an array of | |
| * strings. | |
| * | |
| * @param integer $index | |
| * @param integer|null $length | |
| * | |
| * @return array<integer,string> | |
| */ | |
| public function sliceNameAtoms($index, $length = null) | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (null === $length) { | |
| $length = count($atoms); | |
| } | |
| return array_slice($atoms, $index, $length); | |
| } | |
| /** | |
| * Returns the last atom of this path, excluding the last extension. | |
| * | |
| * If this path has no atoms, an empty string is returned. | |
| * | |
| * @return string | |
| */ | |
| public function nameWithoutExtension() | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (count($atoms) > 1) { | |
| array_pop($atoms); | |
| return implode(static::EXTENSION_SEPARATOR, $atoms); | |
| } | |
| return $atoms[0]; | |
| } | |
| /** | |
| * Returns the last atom of this path, excluding any extensions. | |
| * | |
| * If this path has no atoms, an empty string is returned. | |
| * | |
| * @return string | |
| */ | |
| public function namePrefix() | |
| { | |
| $atoms = $this->nameAtoms(); | |
| return $atoms[0]; | |
| } | |
| /** | |
| * Returns the extensions of this path's last atom. | |
| * | |
| * If the last atom has no extensions, or this path has no atoms, this | |
| * method will return null. | |
| * | |
| * @return string|null | |
| */ | |
| public function nameSuffix() | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (count($atoms) > 1) { | |
| array_shift($atoms); | |
| return implode(static::EXTENSION_SEPARATOR, $atoms); | |
| } | |
| return null; | |
| } | |
| /** | |
| * Returns the last extension of this path's last atom. | |
| * | |
| * If the last atom has no extensions, or this path has no atoms, this | |
| * method will return null. | |
| * | |
| * @return string|null | |
| */ | |
| public function extension() | |
| { | |
| $atoms = $this->nameAtoms(); | |
| $numParts = count($atoms); | |
| if ($numParts > 1) { | |
| return $atoms[$numParts - 1]; | |
| } | |
| return null; | |
| } | |
| /** | |
| * Returns true if this path's last atom has any extensions. | |
| * | |
| * @return boolean | |
| */ | |
| public function hasExtension() | |
| { | |
| return count($this->nameAtoms()) > 1; | |
| } | |
| /** | |
| * Returns the parent of this path. | |
| * | |
| * @return PathInterface | |
| */ | |
| public function parent() | |
| { | |
| $atoms = $this->atoms(); | |
| $atoms[] = static::PARENT_ATOM; | |
| return $this->createPath( | |
| $atoms, | |
| $this instanceof AbsolutePathInterface | |
| ); | |
| } | |
| /** | |
| * Returns a new path instance with the trailing slash removed from this | |
| * path. | |
| * | |
| * If this path has no trailing slash, the path is returned unmodified. | |
| * | |
| * @return PathInterface | |
| */ | |
| public function stripTrailingSlash() | |
| { | |
| if (!$this->hasTrailingSeparator()) { | |
| return $this; | |
| } | |
| return $this->createPath( | |
| $this->atoms(), | |
| $this instanceof AbsolutePathInterface | |
| ); | |
| } | |
| /** | |
| * Returns a new path instance with the last extension removed from this | |
| * path. | |
| * | |
| * If this path has no extensions, the path is returned unmodified. | |
| * | |
| * @return PathInterface | |
| */ | |
| public function stripExtension() | |
| { | |
| return $this->replaceExtension(null); | |
| } | |
| /** | |
| * Returns a new path instance with all extensions removed from this path. | |
| * | |
| * If this path has no extensions, the path is returned unmodified. | |
| * | |
| * @return PathInterface | |
| */ | |
| public function stripNameSuffix() | |
| { | |
| return $this->replaceNameSuffix(null); | |
| } | |
| /** | |
| * Returns a new path with the supplied atom(s) suffixed to this path. | |
| * | |
| * @param string $atom | |
| * @param string,... $additionalAtoms | |
| * | |
| * @return PathInterface | |
| * @throws Exception\InvalidPathAtomExceptionInterface If any joined atoms | |
| * are invalid. | |
| */ | |
| public function joinAtoms($atom) | |
| { | |
| return $this->joinAtomSequence(func_get_args()); | |
| } | |
| /** | |
| * Returns a new path with the supplied sequence of atoms suffixed to this | |
| * path. | |
| * | |
| * @param mixed<string> $atoms | |
| * | |
| * @return PathInterface | |
| * @throws Exception\InvalidPathAtomExceptionInterface If any joined atoms | |
| * are invalid. | |
| */ | |
| public function joinAtomSequence($atoms) | |
| { | |
| if (!is_array($atoms)) { | |
| $atoms = iterator_to_array($atoms); | |
| } | |
| return $this->createPath( | |
| array_merge($this->atoms(), $atoms), | |
| $this instanceof AbsolutePathInterface | |
| ); | |
| } | |
| /** | |
| * Returns a new path with the supplied path suffixed to this path. | |
| * | |
| * @param RelativePathInterface $path | |
| * | |
| * @return PathInterface | |
| */ | |
| public function join(RelativePathInterface $path) | |
| { | |
| return $this->joinAtomSequence($path->atoms()); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied extensions suffixed to this | |
| * path. | |
| * | |
| * @param string $extension | |
| * @param string,... $additionalExtensions | |
| * | |
| * @return PathInterface | |
| * @throws Exception\InvalidPathAtomExceptionInterface If the suffixed | |
| * extensions cause the atom to be invalid. | |
| */ | |
| public function joinExtensions($extension) | |
| { | |
| return $this->joinExtensionSequence(func_get_args()); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied extensions suffixed to this | |
| * path. | |
| * | |
| * @param mixed<string> $extensions | |
| * | |
| * @return PathInterface | |
| * @throws Exception\InvalidPathAtomExceptionInterface If the suffixed | |
| * extensions cause the atom to be invalid. | |
| */ | |
| public function joinExtensionSequence($extensions) | |
| { | |
| if (!is_array($extensions)) { | |
| $extensions = iterator_to_array($extensions); | |
| } | |
| $atoms = $this->nameAtoms(); | |
| if (array('', '') === $atoms) { | |
| array_pop($atoms); | |
| } | |
| return $this->replaceName( | |
| implode( | |
| static::EXTENSION_SEPARATOR, | |
| array_merge($atoms, $extensions) | |
| ) | |
| ); | |
| } | |
| /** | |
| * Returns a new path instance that has a portion of this path's atoms | |
| * replaced with a different sequence of atoms. | |
| * | |
| * @param integer $index | |
| * @param mixed<string> $replacement | |
| * @param integer|null $length | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replace($index, $replacement, $length = null) | |
| { | |
| $atoms = $this->atoms(); | |
| if (!is_array($replacement)) { | |
| $replacement = iterator_to_array($replacement); | |
| } | |
| if (null === $length) { | |
| $length = count($atoms); | |
| } | |
| array_splice($atoms, $index, $length, $replacement); | |
| return $this->createPath( | |
| $atoms, | |
| $this instanceof AbsolutePathInterface | |
| ); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied string suffixed to the last | |
| * path atom. | |
| * | |
| * @param string $suffix | |
| * | |
| * @return PathInterface | |
| * @throws Exception\InvalidPathAtomExceptionInterface If the suffix causes | |
| * the atom to be invalid. | |
| */ | |
| public function suffixName($suffix) | |
| { | |
| $name = $this->name(); | |
| if (static::SELF_ATOM === $name) { | |
| return $this->replaceName($suffix); | |
| } | |
| return $this->replaceName($name . $suffix); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied string prefixed to the last | |
| * path atom. | |
| * | |
| * @param string $prefix | |
| * | |
| * @return PathInterface | |
| * @throws Exception\InvalidPathAtomExceptionInterface If the prefix causes | |
| * the atom to be invalid. | |
| */ | |
| public function prefixName($prefix) | |
| { | |
| $name = $this->name(); | |
| if (static::SELF_ATOM === $name) { | |
| return $this->replaceName($prefix); | |
| } | |
| return $this->replaceName($prefix . $name); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied name replacing the existing | |
| * one. | |
| * | |
| * @param string $name | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replaceName($name) | |
| { | |
| $atoms = $this->atoms(); | |
| $numAtoms = count($atoms); | |
| if ($numAtoms > 0) { | |
| if ('' === $name) { | |
| array_pop($atoms); | |
| } else { | |
| $atoms[$numAtoms - 1] = $name; | |
| } | |
| } elseif ('' !== $name) { | |
| $atoms[] = $name; | |
| } | |
| return $this->createPath( | |
| $atoms, | |
| $this instanceof AbsolutePathInterface | |
| ); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied name replacing the portion | |
| * of the existing name preceding the last extension. | |
| * | |
| * @param string $nameWithoutExtension | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replaceNameWithoutExtension($nameWithoutExtension) | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (count($atoms) < 2) { | |
| return $this->replaceName($nameWithoutExtension); | |
| } | |
| array_splice($atoms, 0, -1, array($nameWithoutExtension)); | |
| return $this->replaceName(implode(self::EXTENSION_SEPARATOR, $atoms)); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied name prefix replacing the | |
| * existing one. | |
| * | |
| * @param string $namePrefix | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replaceNamePrefix($namePrefix) | |
| { | |
| return $this->replaceNameAtoms(0, array($namePrefix), 1); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied name suffix replacing the | |
| * existing one. | |
| * | |
| * @param string|null $nameSuffix | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replaceNameSuffix($nameSuffix) | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (array('', '') === $atoms) { | |
| if (null === $nameSuffix) { | |
| return $this; | |
| } | |
| return $this->replaceName( | |
| static::EXTENSION_SEPARATOR . $nameSuffix | |
| ); | |
| } | |
| $numAtoms = count($atoms); | |
| if (null === $nameSuffix) { | |
| $replacement = array(); | |
| } else { | |
| $replacement = array($nameSuffix); | |
| } | |
| array_splice($atoms, 1, count($atoms), $replacement); | |
| return $this->replaceName(implode(self::EXTENSION_SEPARATOR, $atoms)); | |
| } | |
| /** | |
| * Returns a new path instance with the supplied extension replacing the | |
| * existing one. | |
| * | |
| * @param string|null $extension | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replaceExtension($extension) | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (array('', '') === $atoms) { | |
| if (null === $extension) { | |
| return $this; | |
| } | |
| return $this->replaceName( | |
| static::EXTENSION_SEPARATOR . $extension | |
| ); | |
| } | |
| $numAtoms = count($atoms); | |
| if ($numAtoms > 1) { | |
| if (null === $extension) { | |
| $replacement = array(); | |
| } else { | |
| $replacement = array($extension); | |
| } | |
| array_splice($atoms, -1, $numAtoms, $replacement); | |
| } elseif (null !== $extension) { | |
| $atoms[] = $extension; | |
| } | |
| return $this->replaceName(implode(self::EXTENSION_SEPARATOR, $atoms)); | |
| } | |
| /** | |
| * Returns a new path instance that has a portion of this name's atoms | |
| * replaced with a different sequence of atoms. | |
| * | |
| * @param integer $index | |
| * @param mixed<string> $replacement | |
| * @param integer|null $length | |
| * | |
| * @return PathInterface | |
| */ | |
| public function replaceNameAtoms($index, $replacement, $length = null) | |
| { | |
| $atoms = $this->nameAtoms(); | |
| if (!is_array($replacement)) { | |
| $replacement = iterator_to_array($replacement); | |
| } | |
| if (null === $length) { | |
| $length = count($atoms); | |
| } | |
| array_splice($atoms, $index, $length, $replacement); | |
| return $this->replaceName(implode(self::EXTENSION_SEPARATOR, $atoms)); | |
| } | |
| // Implementation details ================================================== | |
| /** | |
| * @param mixed<string> $atoms | |
| * | |
| * @return array<string> | |
| */ | |
| protected function normalizeAtoms($atoms) | |
| { | |
| $normalizedAtoms = array(); | |
| foreach ($atoms as $atom) { | |
| $this->validateAtom($atom); | |
| $normalizedAtoms[] = $atom; | |
| } | |
| return $normalizedAtoms; | |
| } | |
| /** | |
| * @param string $atom | |
| */ | |
| protected function validateAtom($atom) | |
| { | |
| if ('' === $atom) { | |
| throw new Exception\EmptyPathAtomException; | |
| } elseif (false !== strpos($atom, static::ATOM_SEPARATOR)) { | |
| throw new Exception\PathAtomContainsSeparatorException($atom); | |
| } | |
| } | |
| /** | |
| * @param mixed<string> $atoms | |
| * @param boolean $isAbsolute | |
| * @param boolean|null $hasTrailingSeparator | |
| * | |
| * @return PathInterface | |
| */ | |
| protected function createPath( | |
| $atoms, | |
| $isAbsolute, | |
| $hasTrailingSeparator = null | |
| ) { | |
| if ($isAbsolute) { | |
| return new AbsolutePath( | |
| $atoms, | |
| $hasTrailingSeparator | |
| ); | |
| } | |
| return new RelativePath( | |
| $atoms, | |
| $hasTrailingSeparator | |
| ); | |
| } | |
| private $atoms; | |
| private $hasTrailingSeparator; | |
| } |